#include <iostream>
using namespace std;

#include "tabbporo.h"
#include "tcolaabbporo.h"

/** \file tcolaabbporo.cpp
* \brief Procedimientos de la clase tcolaabbporo.
*
* STANISLAV LITVINENKO DNI:02062226T
* JOSE FRANCES IRIONDO DNI:48469642V
*/

TColaABBPoro::TColaABBPoro(const TColaABBPoro &c)
{
    TECAP* aux=c.primero;

    if (c.primero==NULL)
    {
        primero=ultimo=NULL;
    }
    else
    {
        ultimo=primero=new TECAP(*aux);
        aux=aux->sig;
        while (aux!=NULL)
        {
            ultimo->sig=new TECAP(*aux);
            ultimo=ultimo->sig;
            aux=aux->sig;
        }
    }

}

TColaABBPoro::~TColaABBPoro()
{
        TECAP* aux=primero;
        if (aux==NULL)
        {
                ultimo=primero=NULL;
        }
        else
        {
                while (aux!=ultimo->sig)
                {
                        primero=primero->sig;
                        delete(aux);
                        aux=primero;
                }
        }
}

TColaABBPoro & TColaABBPoro::operator=(const TColaABBPoro &cola)
{

    TECAP *aux = primero;

    if(this!=&cola)
    {
        this->~TColaABBPoro();
        if(cola.primero)
        {
            aux=cola.primero;
            while(aux!=NULL)
            {
                Encolar(aux->arbol);
                aux=aux->sig;
            }
        }
    }
       /* TECAP* aux=primero;
        TECAP* aux2=cola.primero;
        if (aux!=NULL || cola.primero!=NULL)//caso de que la cola inicial no es vacia y la que recibimos tampoco
        {
                while (aux!=ultimo)
                {
                    //hay que hacer algo para ver el tamaño de las colas
                    aux2=aux;
                    aux=aux->sig;
                    aux2=aux2->sig;
                }
        }
        else if(aux!=NULL && cola.primero==NULL)//caso en que la cola inicial es vacia
        {
            //destruimos la cola que nos pasan
            while (aux!=ultimo)
            {
                primero=primero->sig;
                delete(aux);
                aux=primero;
            }
            primero=NULL;
            ultimo=NULL;
        }*/
}

bool TColaABBPoro::operator==(TColaABBPoro &cola)
{
    TECAP* aux=primero;
    TECAP* aux2=cola.primero;

    bool ret=false;

    while(aux!=NULL || aux2!=NULL)//vamos avanzando punteros
    {
        if(aux->arbol && aux2==NULL)//si el arbol de la izquierda esta lleno y el de la derecha vacio
        {
            ret=false;
        }
        else if(aux2->arbol && aux==NULL)//viceversa
        {
            ret=false;
        }
        else if(aux->arbol == aux2->arbol)//si los arboles son iguales
        {
            ret=true;
        }
        aux=aux->sig;
        aux2=aux2->sig;
    }

}

TColaABBPoro TColaABBPoro::operator+(const TColaABBPoro &cola)
{
    TColaABBPoro nuevacola(*this);
    TECAP* aux=cola.primero;
    //TECAP* aux2=primero;

    while(aux!=NULL)
    {
        if(nuevacola.Buscar(aux->arbol) == false)
        {
            nuevacola.Encolar(aux->arbol);
        }
        aux=aux->sig;
    }

    return nuevacola;


}
bool TColaABBPoro::Buscar(TABBPoro* &poro)
{
    TECAP* aux=primero;
    bool ret=false;

    while(aux!=NULL && ret!=true)
    {
        if(aux->arbol->nodo->item==poro->nodo->item)
        {
            ret=true;
        }
        aux=aux->sig;
    }

    return ret;
}
bool TColaABBPoro::EsVacia()
{
    bool ret=false;
    if(primero==NULL && ultimo==NULL)
    {
        ret=true;
    }

    return ret;
}

bool TColaABBPoro::Encolar(TABBPoro *a)
{
        bool ret=false;
        
        TECAP *n= new TECAP();
        
        if(n ==NULL)
        {
            ret = false;
        }
        else
        {
            n->arbol = a;
            n->sig = NULL;
            
            if(EsVacia())
            {
                primero = n;
                ultimo = n;
            }
            else
            {
                ultimo->sig=n;
                ultimo=n;
            }
            
            ret=true;
        }

        /*
            if (ultimo!=NULL)
            {
                //ultimo->sig->arbol= new TECAP((TABBPoro*)a);
                    ultimo->sig=new TECAP();
                    ultimo->sig->arbol=a;
                    ultimo=ultimo->sig;
                    ret=true;
            }
            else
            {
                    ultimo=primero=new TECAP();
                    primero->arbol=a;
                    ret=true;
            }
*/
        
        return ret;

}

bool TColaABBPoro::Desencolar()
{
        TECAP* aux=primero;
        bool ret=false;
        if (primero!=NULL)
        {
                primero=primero->sig;
                delete(aux);
                ret=true;

                if (primero==NULL)
                {
                        ultimo=NULL;
                }

        }

        return ret;

}

TABBPoro * TColaABBPoro::Cabeza() const
{
        TABBPoro* aux= NULL;
        if (primero!= NULL)
        {
                aux=primero->arbol;
        }
        return aux;
}

int TColaABBPoro::Longitud() const
{
        TECAP* aux=primero;
        int longitud=0;

        if(aux!=NULL)
        {
                while (aux!=NULL)
                {
                    aux=aux->sig;
                    longitud++;
                }
        }

        return longitud;
}
ostream & operator<<(ostream &os,const TColaABBPoro &colaabb)
{

    TColaABBPoro p(colaabb);
    os << '(';
    while(!p.EsVacia())
    {
        if(p.Cabeza()!=NULL)
        {
            os << p.Cabeza()->Raiz();
        }
        else
        {
            os << ".";
        }
        if(p.primero!=p.ultimo)
        {
            os << " ";
        }
        p.Desencolar();
    }
    os << ')';

    return os;
}
//=====================FIN DE TCOLAABBPORO===============

TECAP::TECAP (const TECAP &nodo)
{
    arbol=nodo.arbol;
    sig=NULL;

}

TECAP::~TECAP ()
{
    arbol=NULL;
    sig=NULL;
}

TECAP & TECAP::operator=(const TECAP &nodo)
{
    if(this!=&nodo)
    {
        arbol=nodo.arbol;
        sig=nodo.sig;
    }
}
